<template>
  <view 
    class="fu-number-box"
    :class="{ 'fu-number-box--disabled': disabled }"
  >
    <view 
      class="fu-number-box__minus"
      :class="{ 'fu-number-box__minus--disabled': minusDisabled }"
      @click="onMinus"
    >
      <text>-</text>
    </view>
    <input
      class="fu-number-box__input"
      type="number"
      :value="displayValue"
      :disabled="disabled"
      @input="onInput"
      @blur="onBlur"
    />
    <view 
      class="fu-number-box__plus"
      :class="{ 'fu-number-box__plus--disabled': plusDisabled }"
      @click="onPlus"
    >
      <text>+</text>
    </view>
  </view>
</template>

<script>
/**
 * fu-number-box 数字输入框组件
 * @description 数字加减输入框，可自定义步长、范围
 * @property {Number} modelValue - 当前值
 * @property {Number} min - 最小值
 * @property {Number} max - 最大值
 * @property {Number} step - 步长
 * @property {Boolean} disabled - 是否禁用
 * @property {Number} precision - 小数位数
 * @event {Function} update:modelValue - 值变化时触发
 * @event {Function} change - 值变化时触发
 */
export default {
  name: 'fu-number-box',
  props: {
    modelValue: {
      type: [Number, String],
      default: 0
    },
    min: {
      type: Number,
      default: 0
    },
    max: {
      type: Number,
      default: 100
    },
    step: {
      type: Number,
      default: 1
    },
    disabled: {
      type: Boolean,
      default: false
    },
    precision: {
      type: Number,
      default: 0
    }
  },
  emits: ['update:modelValue', 'change'],
  computed: {
    displayValue() {
      return this.getPrecisionValue(Number(this.modelValue))
    },
    minusDisabled() {
      return this.disabled || this.modelValue <= this.min
    },
    plusDisabled() {
      return this.disabled || this.modelValue >= this.max
    }
  },
  methods: {
    getPrecisionValue(value) {
      if (typeof value === 'number') {
        return Number(value.toFixed(this.precision))
      }
      return value
    },
    setValue(value) {
      value = this.getPrecisionValue(value)
      if (value === this.modelValue) return
      this.$emit('update:modelValue', value)
      this.$emit('change', value)
    },
    onInput(event) {
      let value = event.detail.value
      // 处理空值
      if (value === '') {
        value = this.min
      } else {
        value = Number(value)
        // 限制范围
        if (value < this.min) value = this.min
        if (value > this.max) value = this.max
      }
      this.setValue(value)
    },
    onBlur(event) {
      let value = event.detail.value
      value = value === '' ? this.min : Number(value)
      this.setValue(value)
    },
    onMinus() {
      if (this.minusDisabled) return
      const value = Number(this.modelValue) - this.step
      this.setValue(Math.max(this.min, value))
    },
    onPlus() {
      if (this.plusDisabled) return
      const value = Number(this.modelValue) + this.step
      this.setValue(Math.min(this.max, value))
    }
  }
}
</script>

<style lang="scss" scoped>
.fu-number-box {
  display: inline-flex;
  align-items: center;
  width: fit-content;
  
  &--disabled {
    opacity: 0.5;
    pointer-events: none;
  }
  
  &__minus,
  &__plus {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 64rpx;
    height: 64rpx;
    background-color: #fff;
    border: 2rpx solid var(--fu-border-color);
    box-sizing: border-box;
    transition: all 0.2s;
    position: relative;
    overflow: hidden;
    
    text {
      font-size: 32rpx;
      line-height: 1;
      color: var(--fu-text-color);
      font-weight: bold;
    }
    
    &::after {
      content: '';
      position: absolute;
      left: 0;
      right: 0;
      top: 0;
      bottom: 0;
      background-color: #000;
      opacity: 0;
      transition: opacity 0.2s;
    }
    
    &:active::after {
      opacity: 0.1;
    }
    
    &--disabled {
      cursor: not-allowed;
      opacity: 0.5;
      
      &::after {
        display: none;
      }
    }
  }
  
  &__minus {
    border-radius: var(--fu-radius-base) 0 0 var(--fu-radius-base);
    border-right: none;
  }
  
  &__plus {
    border-radius: 0 var(--fu-radius-base) var(--fu-radius-base) 0;
    border-left: none;
  }
  
  &__input {
    width: 88rpx;
    height: 64rpx;
    padding: 0;
    color: var(--fu-text-color);
    font-size: var(--fu-font-size-base);
    background-color: #fff;
    border: 2rpx solid var(--fu-border-color);
    border-radius: 0;
    text-align: center;
    box-sizing: border-box;
    transition: all 0.2s;
    
    &:focus {
      border-color: var(--fu-primary-color);
    }
    
    &:disabled {
      background-color: #f7f8fa;
      color: var(--fu-text-color-disabled);
    }
  }
}
</style> 